home *** CD-ROM | disk | FTP | other *** search
/ The Datafile PD-CD 1 Issue 2 / PDCD-1 - Issue 02.iso / _utilities / utilities / 001 / meschach / !Meschach / c / zfunc < prev    next >
Text File  |  1994-08-03  |  5KB  |  238 lines

  1.  
  2. /**************************************************************************
  3. **
  4. ** Copyright (C) 1993 David E. Steward & Zbigniew Leyk, all rights reserved.
  5. **
  6. **                 Meschach Library
  7. ** 
  8. ** This Meschach Library is provided "as is" without any express 
  9. ** or implied warranty of any kind with respect to this software. 
  10. ** In particular the authors shall not be liable for any direct, 
  11. ** indirect, special, incidental or consequential damages arising 
  12. ** in any way from use of the software.
  13. ** 
  14. ** Everyone is granted permission to copy, modify and redistribute this
  15. ** Meschach Library, provided:
  16. **  1.  All copies contain this copyright notice.
  17. **  2.  All modified copies shall carry a notice stating who
  18. **      made the last modification and the date of such modification.
  19. **  3.  No charge is made for this software or works derived from it.  
  20. **      This clause shall not be construed as constraining other software
  21. **      distributed on the same medium as this software, nor is a
  22. **      distribution fee considered a charge.
  23. **
  24. ***************************************************************************/
  25.  
  26. /*
  27.     Elementary functions for complex numbers
  28.     -- if not already defined
  29. */
  30.  
  31. #include    <math.h>
  32. #include    "zmatrix.h"
  33.  
  34. static char rcsid[] = "$Id: zfunc.c,v 1.1 1994/01/13 04:28:29 des Exp $";
  35.  
  36. #ifndef COMPLEX_H
  37.  
  38. #ifndef zmake
  39. /* zmake -- create complex number real + i*imag */
  40. complex    zmake(real,imag)
  41. double    real, imag;
  42. {
  43.     complex    w;    /* == real + i*imag */
  44.  
  45.     w.re = real;    w.im = imag;
  46.     return w;
  47. }
  48. #endif
  49.  
  50. #ifndef zneg
  51. /* zneg -- returns negative of z */
  52. complex    zneg(z)
  53. complex    z;
  54. {
  55.     z.re = - z.re;
  56.     z.im = - z.im;
  57.  
  58.     return z;
  59. }
  60. #endif
  61.  
  62. #ifndef zabs
  63. /* zabs -- returns |z| */
  64. double    zabs(z)
  65. complex    z;
  66. {
  67.     Real    x, y, tmp;
  68.     int        x_expt, y_expt;
  69.  
  70.     /* Note: we must ensure that overflow does not occur! */
  71.     x = ( z.re >= 0.0 ) ? z.re : -z.re;
  72.     y = ( z.im >= 0.0 ) ? z.im : -z.im;
  73.     if ( x < y )
  74.     {
  75.     tmp = x;
  76.     x = y;
  77.     y = tmp;
  78.     }
  79.     x = frexp(x,&x_expt);
  80.     y = frexp(y,&y_expt);
  81.     y = ldexp(y,y_expt-x_expt);
  82.     tmp = sqrt(x*x+y*y);
  83.  
  84.     return ldexp(tmp,x_expt);
  85. }
  86. #endif
  87.  
  88. #ifndef zadd
  89. /* zadd -- returns z1+z2 */
  90. complex zadd(z1,z2)
  91. complex    z1, z2;
  92. {
  93.     complex z;
  94.  
  95.     z.re = z1.re + z2.re;
  96.     z.im = z1.im + z2.im;
  97.  
  98.     return z;
  99. }
  100. #endif
  101.  
  102. #ifndef zsub
  103. /* zsub -- returns z1-z2 */
  104. complex zsub(z1,z2)
  105. complex    z1, z2;
  106. {
  107.     complex z;
  108.  
  109.     z.re = z1.re - z2.re;
  110.     z.im = z1.im - z2.im;
  111.  
  112.     return z;
  113. }
  114. #endif
  115.  
  116. #ifndef zmlt
  117. /* zmlt -- returns z1*z2 */
  118. complex    zmlt(z1,z2)
  119. complex    z1, z2;
  120. {
  121.     complex z;
  122.  
  123.     z.re = z1.re * z2.re - z1.im * z2.im;
  124.     z.im = z1.re * z2.im + z1.im * z2.re;
  125.  
  126.     return z;
  127. }
  128. #endif
  129.  
  130. #ifndef zinv
  131. /* zmlt -- returns 1/z */
  132. complex    zinv(z)
  133. complex    z;
  134. {
  135.     Real    x, y, tmp;
  136.     int        x_expt, y_expt;
  137.  
  138.     if ( z.re == 0.0 && z.im == 0.0 )
  139.     error(E_SING,"zinv");
  140.     /* Note: we must ensure that overflow does not occur! */
  141.     x = ( z.re >= 0.0 ) ? z.re : -z.re;
  142.     y = ( z.im >= 0.0 ) ? z.im : -z.im;
  143.     if ( x < y )
  144.     {
  145.     tmp = x;
  146.     x = y;
  147.     y = tmp;
  148.     }
  149.     x = frexp(x,&x_expt);
  150.     y = frexp(y,&y_expt);
  151.     y = ldexp(y,y_expt-x_expt);
  152.  
  153.     /* 'ldexp' call moved to 'tmp' assignment by Paul Field */
  154.     tmp = (1.0/(x*x + y*y)) * ldexp(1.0,-2*x_expt);
  155.     z.re =  z.re*tmp  /* * ldexp(1.0,-2*x_expt) */;
  156.     z.im = -z.im*tmp  /* * ldexp(1.0,-2*x_expt) */;
  157.  
  158.     return z;
  159. }
  160. #endif
  161.  
  162. #ifndef zdiv
  163. /* zdiv -- returns z1/z2 */
  164. complex    zdiv(z1,z2)
  165. complex    z1, z2;
  166. {
  167.     return zmlt(z1,zinv(z2));
  168. }
  169. #endif
  170.  
  171. #ifndef zsqrt
  172. /* zsqrt -- returns sqrt(z); uses branch with Re sqrt(z) >= 0 */
  173. complex    zsqrt(z)
  174. complex    z;
  175. {
  176.     complex    w;    /* == sqrt(z) at end */
  177.     Real    alpha;
  178.  
  179.     alpha = sqrt(0.5*(fabs(z.re) + zabs(z)));
  180.     if ( z.re >= 0.0 )
  181.     {
  182.     w.re = alpha;
  183.     w.im = z.im / (2.0*alpha);
  184.     }
  185.     else
  186.     {
  187.     w.re = fabs(z.im)/(2.0*alpha);
  188.     w.im = ( z.im >= 0 ) ? alpha : - alpha;
  189.     }
  190.  
  191.     return w;
  192. }
  193. #endif
  194.  
  195. #ifndef    zexp
  196. /* zexp -- returns exp(z) */
  197. complex    zexp(z)
  198. complex    z;
  199. {
  200.     complex    w;    /* == exp(z) at end */
  201.     Real    r;
  202.  
  203.     r = exp(z.re);
  204.     w.re = r*cos(z.im);
  205.     w.im = r*sin(z.im);
  206.  
  207.     return w;
  208. }
  209. #endif
  210.  
  211. #ifndef    zlog
  212. /* zlog -- returns log(z); uses principal branch with -pi <= Im log(z) <= pi */
  213. complex    zlog(z)
  214. complex    z;
  215. {
  216.     complex    w;    /* == log(z) at end */
  217.  
  218.     w.re = log(zabs(z));
  219.     w.im = atan2(z.im,z.re);
  220.  
  221.     return w;
  222. }
  223. #endif
  224.  
  225. #ifndef zconj
  226. complex    zconj(z)
  227. complex    z;
  228. {
  229.     complex    w;    /* == conj(z) */
  230.  
  231.     w.re =   z.re;
  232.     w.im = - z.im;
  233.     return w;
  234. }
  235. #endif
  236.  
  237. #endif
  238.